package TenoriOn.managers
{
	import TenoriOn.Grid;
	import TenoriOn.GridData;
	
	import flash.geom.Point;
	
	public class GateManager implements IGridManager
	{
		private var _grid:Grid;
		public static const MAX_GATE_LENGTH:Number=8192*2;
		public static const MIN_GATE_LENGTH:Number=8192/2;
		private var _sequencerManager:SequencerManager;
		
		private var _hasControl:Boolean;
		public function get hasControl():Boolean{
			return _hasControl;
		}
		
		public function GateManager(sequencerManager:SequencerManager)
		{
			_sequencerManager=sequencerManager;
			gateFunction=SMOOTH;
			SMOOTH.prototype.name="SMOOTH";
			ON.prototype.name="ON";
			SQUARE.prototype.name="SQUARE";
			ATTACK.prototype.name="ATTACK";
			DELAY.prototype.name="DELAY";
			
		}
		public function get MANAGER_TYPE():String
		{
			return "GateManager";
		}
		
		public function makeGridData():GridData
		{
			var level:int=Math.round(15*(gateLength-MIN_GATE_LENGTH)/(MAX_GATE_LENGTH-MIN_GATE_LENGTH));
			var gData:GridData=new GridData();
			for(var i:int=0;i<16;i++){
				gData.data[i][level]=1;
			}
			return gData;
		}
		
		public function takeControl(grid:Grid):void
		{
			grid.manager=this;
			_hasControl=true;
			_grid=grid;
			updateGrid();
		}
		
		public function releaseControl():void
		{
			_hasControl=false;
		}
		
		public function onGridUpdate(id:Point):void
		{
			gateLength=(MAX_GATE_LENGTH-MIN_GATE_LENGTH)*id.y/15+MIN_GATE_LENGTH;
			updateGrid();
		}
		
		public function updateGrid():void
		{
			_grid.redrawGrid(makeGridData());
			_grid.textDisplay.setText("Gate Manager","LENGTH:"+Math.round(gateLength).toString(),"FUNCTION:"+gateFunction.prototype.name);
		}
		
		public var gateLength:Number=8192;
		public var gateFunction:Function;
		
		private var _gatePosition:int;
		public function get gatePosition():int{
			return _gatePosition;
		}
		public function set gatePosition(value:int):void{
			if(value>15){
				_gatePosition=0;
			}
			else
				_gatePosition=value;
		}		
		
		public function resest():void{
			_gatePosition=0;
			_gateProgress=0;
		}	
		
		private var _gateProgress:int;
		public function get gateProgress():int{
			return _gateProgress;
		}
		public function set gateProgress(value:int):void{
			if(value>gateLength){
				_gateProgress=0;
				gatePosition++;
				if(_sequencerManager.hasControl)
					_sequencerManager.updateGrid();
			}
			else
				_gateProgress=value;
		}
		
		public var SMOOTH:Function=function(x:Number):Number{
			if(x<gateLength/2)
				return 2*x/gateLength;
			else
				return 2*(gateLength-x)/gateLength;
		};
		public var SQUARE:Function=function(x:Number):Number{
			return ((x<0.95*gateLength)&&(x>0.05*gateLength))?1:0;
		};
		public var ON:Function=function(x:Number):Number{
			return 1;
		};
		public var DELAY:Function=function(x:Number):Number{
			return x/gateLength;
		};
		
		public var ATTACK:Function=function(x:Number):Number{
			return (gateLength-x)/gateLength;
		};
			
	}
}